var helper = {
    insertOD: function ($targetData, $data) {
        !$targetData && ($targetData = {})
        for (var key in $data) {
            $targetData[key] = {
                value: $data[key],
                linkNodes: [],
                mounted: false
            }
        }

        return $targetData
    }
}
function Data() {

}

Data.formatDate = function (data) {
    data['_od_'] = helper.insertOD(data['_od'], data)
    return data
}
/**
 * Created by zhengqiguang on 2017/6/15.
 */

const compiler_helper = {
    generaltplFn(tpl) {
        let patt = new RegExp("\{\{\[ \\t\]\*\(\[\@\#\]\?\)\(\\\/\?\)\(\[\\w\\W\]\*\?\)\[ \\t\]\*\}\}", "g"),
            result;

        let tempStrFn = "",
            fnArgs = [],
            cursor = 0;


        while ((result = patt.exec(tpl)) !== null) {
            console.log('result', result)
            var $temp1 = tpl.slice(cursor, result.index);
            console.log('$temp1', $temp1)
            cursor += $temp1.length;
            // debugger
            tempStrFn += this.wrapStaticBlock($temp1);

            // let $temp2 = tpl.slice(cursor, cursor + result[0].length);

            fnArgs.push(result[3]);
            tempStrFn += this.wrapDynamicBlock(result);
            cursor += result[0].length;
        }
        console.log('fnArgs', fnArgs)

        let tempLast = tpl.slice(cursor, tpl.length);


        tempStrFn += this.wrapStaticBlock(tempLast);
        console.log('tempStrFn', typeof tempStrFn)

        console.log('tempStrFn', tempStrFn)

        let tplFn = this.gTplFn(tempStrFn);
        console.log('tplFn', tplFn)
        return {
            tplFn: tplFn,
            linkArgs: fnArgs
        }
    },
    wrapStaticBlock: function (str) {

        return "\'" + str + "\'";

    },
    wrapDynamicBlock: function (result) {

        return " + od." + result[3] + " + "
    },
    gTplFn: function (str) {

        let $t = "console.log(od); return " + str;

        $t = $t.replace(/\n/g, "");

        let $tempFn = new Function("od", $t);


        return $tempFn;

    }


}


class Compiler {


    constructor(tpl) {
        this.tpl = tpl;
        this.init(compiler_helper.generaltplFn(this.tpl));
    }

    init({ tplFn, linkArgs }) {
        this.tplFn = tplFn;
        this.linkArgs = linkArgs;
    }

}

compiler_helper.generaltplFn('<span style="color:red">{{a}}</span>{{sdf}}{{ ccc }}')


function Mue(params) {
    this.data = params.data

    // return vnode
}


function mountWatcher() {
    let od = this.$data['_od_']

    for (let key in this.$data) {
        (function () {
            let timeoutHandler = null
            if (key !== '_od' && !od[key].mounted) {
                if (!od[key]) {
                    throw new Error(`data:${key} is init`)
                }
                Object.defineProperty(this.$data, key, {
                    get() {
                        return od[key].value
                    },
                    set(value) {
                        clearTimeout(timeoutHandler)

                        setTimeout(() => {
                            if (value !== od[key].value) {
                                var $n = od[key].linkNodes
                                od[key].value = value
                                for (var i = 0, n; n = $n[i]; i++) {
                                    n.update()
                                }
                            }
                        }, 1000 / 60);
                    }
                })
                od[key].mounted = true
            }
        }.bind(this))(key)
    }
}